using System;

namespace Commons.Utils
{
	public class DateTimeHelper
	{
		private static readonly DateTime ReferenceDate = new DateTime(1970, 1, 1, 0, 0, 0, 0, DateTimeKind.Utc);

		private static DateTime calculatedDate = DateTime.MinValue;
		private static DateTime previousSystemTime = DateTime.UtcNow;


		public static DateTime Current()
		{
			return DateTime.UtcNow;
		}

		public static void Reset()
		{
			calculatedDate = DateTime.MinValue;
		}

		public static long GetTimestamp()
		{
			return GetTimestamp(Current());
		}

		public static long GetUtcTimestamp()
		{
			return GetTimestamp(DateTime.UtcNow);
		}

		public static long GetTimestamp(DateTime dateTime)
		{
			return (long) (dateTime.ToUniversalTime() - ReferenceDate).TotalMilliseconds;
		}

		public static DateTime GetDateTime(long timestamp)
		{
			return ReferenceDate.AddMilliseconds(timestamp);
		}

		public static DateTime Min(DateTime dateTime1, DateTime dateTime2)
		{
			return dateTime1 < dateTime2 ? dateTime1 : dateTime2;
		}

		public static DateTime Max(DateTime dateTime1, DateTime dateTime2)
		{
			return dateTime1 > dateTime2 ? dateTime1 : dateTime2;
		}

		public static bool IsSameDay(DateTime dateTime1, DateTime dateTime2)
		{
			return dateTime1.DayOfYear == dateTime2.DayOfYear && dateTime1.Year == dateTime2.Year;
		}

		public static bool IsSameMonth(DateTime dateTime1, DateTime dateTime2)
		{
			return dateTime1.Month == dateTime2.Month && dateTime1.Year == dateTime2.Year;
		}

		public static bool IsSameWeek(DateTime dateTime1, DateTime dateTime2)
		{
			int firstDayOfWeek1 = dateTime1.DayOfYear - (int) dateTime1.DayOfWeek;
			if (firstDayOfWeek1 < 0)
			{
				dateTime1.AddYears(-1);
				firstDayOfWeek1 += GetDaysInYear(dateTime1.Year);
			}
			int firstDayOfWeek2 = dateTime2.DayOfYear - (int) dateTime2.DayOfWeek;
			if (firstDayOfWeek2 < 0)
			{
				dateTime2.AddYears(-1);
				firstDayOfWeek2 += GetDaysInYear(dateTime2.Year);
			}

			return firstDayOfWeek1 == firstDayOfWeek2 && dateTime1.Year == dateTime2.Year;
		}

		public static int GetDaysInYear(int year)
		{
			int days = 0;
			for (int month = 1; month <= 12; month++)
			{
				days += DateTime.DaysInMonth(year, month);
			}
			return days;
		}
		
		public static string FromSeconds(float seconds)
		{
			TimeSpan t = TimeSpan.FromSeconds(seconds);
			string timeFormat = "";
			
			if (t.TotalMinutes < 1.0)
			{
				timeFormat = String.Format("{0}s", t.Seconds);
			}
			else if (t.TotalHours < 1.0)
			{
				if (t.Seconds != 0)
					timeFormat = String.Format("{0}m" +"{1:D2}s", t.Minutes, t.Seconds);
				else
					timeFormat = String.Format("{0}m", t.Minutes);
			}
			else
			{
				timeFormat = "{0}h";
				
				if (t.Minutes != 0)
					timeFormat += " {1:D2}m";
				
				if(t.Seconds != 0)
					timeFormat += " {2:D2}s";
				
				timeFormat = String.Format(timeFormat, (int)t.TotalHours, t.Minutes, t.Seconds);
			}
			
			return timeFormat;
		}
	}
}

